module OH_RSOH(
   GLB_RESET,
  // Input data bus from frame
   DBI_RCLK_155M,
   DBI_FAS_FAIL,
   DBI_FRM_FCNT8,
   DBI_FRM_FCNT270,
   DBI_FRM_FCNT9,
   DBI_FRM_DATA,
  // MPI interface signals
   MPI_RXJ0_MODE,
   MPI_RXJ0_DATA,
   MPI_RXK1K2,
   MPI_RXS1,
   MPI_RXB2COUNT,
   MPI_RXB2PULSE,
   MPI_RXREICOUNT,
   MPI_RXREIPULSE,

  // output data bus
   RXB2_CHECK_CNT
   );

input                        GLB_RESET;

input                        DBI_RCLK_155M;
input                        DBI_FAS_FAIL;
input[2:0]                   DBI_FRM_FCNT8;
input[8:0]                   DBI_FRM_FCNT270;
input[3:0]                   DBI_FRM_FCNT9;
input[63:0]                  DBI_FRM_DATA;


input                        MPI_RXJ0_MODE;      // J0 sequence mode, '1'--- 16 bytes sequence; '0'--- 1 byte sequence
output reg[127:0]            MPI_RXJ0_DATA;      // 16 bytes wide J0 sequence data,
                                                 // 16 bytes sequence mode--- BIT7-BIT0 CRC byte, BIT127-BIT8 data byte
                                                 // 1 byte sequence mode----- received J0 byte repeated 16 times in BIT127-BIT0
output reg[15:0]             MPI_RXK1K2;         // K1/K2 byte data, BIT15-BIT8 are K1 byte, BIT7-BIT0 are K2 byte
output wire[7:0]              MPI_RXS1;
output reg[11:0]             MPI_RXB2COUNT;
output reg                   MPI_RXB2PULSE;
output reg[11:0]             MPI_RXREICOUNT;
output reg                   MPI_RXREIPULSE;
output[11:0]                 RXB2_CHECK_CNT;

// signals for J0 receive
reg[3:0]                     RXJ0_MODE;
reg[127:0]                   RXJ0_J0;
reg[3:0]                     RXJ0_COUNT;

// signals for K1,K2 capture
reg[7:0]                     RXK1K2_K1;
reg[7:0]                     RXK1K2_K2;

// signals for B2 check, 
reg[2:0]                     DBIM1_FRM_FCNT8, DBIM2_FRM_FCNT8;
reg[8:0]                     DBIM1_FRM_FCNT270, DBIM2_FRM_FCNT270;
reg[3:0]                     DBIM1_FRM_FCNT9, DBIM2_FRM_FCNT9;
reg[63:0]                    DBIM1_FRM_DATA, DBIM2_FRM_DATA;

reg[4:0]                     RXB2_READ_CHNN, RXB2_WRITE_CHNN;
reg                          RXB2_B2CAL_EN;
reg                          RXB2_B2CAL_START;
reg[63:0]                    RXB2_WR_B2CALC;    // B2 calculate registers, 
wire[63:0]                   RXB2_RO_B2CALC;
wire[63:0]                   RXB2_RO_B2RESULT;  // RAM read out data of previous frame
wire[63:0]                   RXB2_BITS_ERROR;   // 
reg                          RXB2_B2BYTE_EN;
reg[7:0]                     RXB2_CHECK_CNT0, RXB2_CHECK_CNT1, RXB2_CHECK_CNT2, RXB2_CHECK_CNT3, RXB2_CHECK_CNT4, RXB2_CHECK_CNT5, RXB2_CHECK_CNT6, RXB2_CHECK_CNT7;
reg[11:0]                    RXB2_CHECK_CNT;

wire                         B2CALC_RAM_CLKA, B2CALC_RAM_CLKB;        // sginals for B2 calculate RAM
wire                         B2CALC_RAM_WEA;
wire[5:0]                    B2CALC_RAM_ADDRA, B2CALC_RAM_ADDRB;
wire[63:0]                   B2CALC_RAM_DINA, B2CALC_RAM_DOUTB;

wire                         B2RESULT_RAM_CLKA, B2RESULT_RAM_CLKB;    // sginals for B2 result RAM, the RAM save the B2 result of previous frame
wire                         B2RESULT_RAM_WEA;
wire[5:0]                    B2RESULT_RAM_ADDRA, B2RESULT_RAM_ADDRB;
wire[63:0]                   B2RESULT_RAM_DINA, B2RESULT_RAM_DOUTB;

// sginals for B2, REI count
reg[15:0]                    CNT_M0M1_BYTE;

assign MPI_RXS1[7:0] = 8'h00;

//****** Section 1: J0 byte ******//
// cpature CPU configuration RXJ0_MODE with data clock
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      RXJ0_MODE                      <= 1'b0;
   else
      RXJ0_MODE                      <= MPI_RXJ0_MODE;
end
// generate J0 count from RXJ0_MODE and input J0 data
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      RXJ0_COUNT[3:0]                <= 4'd0;
   else begin
      if ( RXJ0_MODE==1'b0 ) begin      // J0 byte using 1-byte sequence, increase the J0 sequence count at the end of frame
         if ( DBI_FRM_FCNT9[3:0]==4'd8 && DBI_FRM_FCNT270[8:0]==9'd269 && DBI_FRM_FCNT8[2:0]==3'd7 )
            RXJ0_COUNT[3:0]          <= RXJ0_COUNT[3:0] +4'd1;
      end
      else begin                       // J0 byte using 1-byte sequence, increase the J0 sequence count at the end of frame, clear the count when received CRC byte flag at J0 position,
         if ( DBI_FRM_FCNT9[3:0]==4'd0 && DBI_FRM_FCNT270[8:0]==9'd6 && DBI_FRM_FCNT8[2:0]==3'd0 && DBI_FRM_DATA[63]==1'b1 )
            RXJ0_COUNT[3:0]          <= 4'd0;
         else if ( DBI_FRM_FCNT9[3:0]==4'd8 && DBI_FRM_FCNT270[8:0]==9'd269 && DBI_FRM_FCNT8[2:0]==3'd7 )
            RXJ0_COUNT[3:0]          <= RXJ0_COUNT[3:0] +4'd1;
      end
   end
end
// capture J0 data into MPI_RXJ0_DATA
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      RXJ0_J0[7:0]                   <= 8'd0;
   else if ( DBI_FRM_FCNT9[3:0]==4'd0 && DBI_FRM_FCNT270[8:0]==9'd6 && DBI_FRM_FCNT8[2:0]==3'd0 )
      RXJ0_J0[7:0]                   <= DBI_FRM_DATA[63:56];
end
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      MPI_RXJ0_DATA[127:0]               <= 128'd0;
   else begin
      if ( DBI_FRM_FCNT9[3:0]==4'd8 && DBI_FRM_FCNT270[8:0]==9'd269 && DBI_FRM_FCNT8[2:0]==3'd7 )  begin
         case ( RXJ0_COUNT[3:0] )
         4'b0000:  MPI_RXJ0_DATA[7:0]            <= RXJ0_J0[7:0];
         4'b0001:  MPI_RXJ0_DATA[15:8]           <= RXJ0_J0[7:0];
         4'b0010:  MPI_RXJ0_DATA[23:16]          <= RXJ0_J0[7:0];
         4'b0011:  MPI_RXJ0_DATA[31:24]          <= RXJ0_J0[7:0];
         4'b0100:  MPI_RXJ0_DATA[39:32]          <= RXJ0_J0[7:0];
         4'b0101:  MPI_RXJ0_DATA[47:40]          <= RXJ0_J0[7:0];
         4'b0110:  MPI_RXJ0_DATA[55:48]          <= RXJ0_J0[7:0];
         4'b0111:  MPI_RXJ0_DATA[63:56]          <= RXJ0_J0[7:0];
         4'b1000:  MPI_RXJ0_DATA[71:64]          <= RXJ0_J0[7:0];
         4'b1001:  MPI_RXJ0_DATA[79:72]          <= RXJ0_J0[7:0];
         4'b1010:  MPI_RXJ0_DATA[87:80]          <= RXJ0_J0[7:0];
         4'b1011:  MPI_RXJ0_DATA[95:88]          <= RXJ0_J0[7:0];
         4'b1100:  MPI_RXJ0_DATA[103:96]         <= RXJ0_J0[7:0];
         4'b1101:  MPI_RXJ0_DATA[111:104]        <= RXJ0_J0[7:0];
         4'b1110:  MPI_RXJ0_DATA[119:112]        <= RXJ0_J0[7:0];
         4'b1111:  MPI_RXJ0_DATA[127:120]        <= RXJ0_J0[7:0];
         default: ;
         endcase
      end
   end
end


//****** Section 2: K1,K2 byte capture******//
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      RXK1K2_K1[7:0]                   <= 8'd0;
   else if ( DBI_FRM_FCNT9[3:0]==4'd4 && DBI_FRM_FCNT270[8:0]==9'd3 && DBI_FRM_FCNT8[2:0]==3'd0 )
      RXK1K2_K1[7:0]                   <= DBI_FRM_DATA[63:56];
end
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      RXK1K2_K2[7:0]                   <= 8'd0;
   else if ( DBI_FRM_FCNT9[3:0]==4'd4 && DBI_FRM_FCNT270[8:0]==9'd4 && DBI_FRM_FCNT8[2:0]==3'd0 )
      RXK1K2_K2[7:0]                   <= DBI_FRM_DATA[63:56];
end
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      MPI_RXK1K2[15:0]                 <= 16'd0;
   else if ( DBI_FRM_FCNT9[3:0]==4'd8 && DBI_FRM_FCNT270[8:0]==9'd269 && DBI_FRM_FCNT8[2:0]==3'd7 )  begin
      MPI_RXK1K2[15:8]                 <= RXK1K2_K1[7:0];
      MPI_RXK1K2[7:0]                  <= RXK1K2_K2[7:0];
   end
end


//****** Section 3: B2 Errors calculate ******//

// delay input data and counts, wait for B2 RAM read
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 ) begin
      DBIM1_FRM_FCNT8[2:0]               <= 3'd0;
      DBIM2_FRM_FCNT8[2:0]               <= 3'd0;
      DBIM1_FRM_FCNT270[8:0]             <= 9'd0;
      DBIM2_FRM_FCNT270[8:0]             <= 9'd0;
      DBIM1_FRM_FCNT9[3:0]               <= 4'd0;
      DBIM2_FRM_FCNT9[3:0]               <= 4'd0;
      DBIM1_FRM_DATA[63:0]               <= 64'd0;
      DBIM2_FRM_DATA[63:0]               <= 64'd0;
   end
   else begin
      DBIM1_FRM_FCNT8[2:0]               <= DBI_FRM_FCNT8[2:0];
      DBIM2_FRM_FCNT8[2:0]               <= DBIM1_FRM_FCNT8[2:0];
      DBIM1_FRM_FCNT270[8:0]             <= DBI_FRM_FCNT270[8:0];
      DBIM2_FRM_FCNT270[8:0]             <= DBIM1_FRM_FCNT270[8:0];
      DBIM1_FRM_FCNT9[3:0]               <= DBI_FRM_FCNT9[3:0];
      DBIM2_FRM_FCNT9[3:0]               <= DBIM1_FRM_FCNT9[3:0];
      DBIM1_FRM_DATA[63:0]               <= DBI_FRM_DATA[63:0];
      DBIM2_FRM_DATA[63:0]               <= DBIM1_FRM_DATA[63:0];
   end
end

// generate read/write address, read address generated from DBI_* bus, write address generated from DBIM2_* bus because of RAM read lactency
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      RXB2_READ_CHNN[4:0]                  <= 5'd0;
   else begin
      if ( DBI_FRM_FCNT9[3:0]==4'd8 && DBI_FRM_FCNT270[8:0]==9'd269 && DBI_FRM_FCNT8[2:0]==3'd7 )
         RXB2_READ_CHNN[4:0]               <= 5'd0;
      else if ( RXB2_READ_CHNN[4:0]==5'd23 )
         RXB2_READ_CHNN[4:0]               <= 5'd0;
      else
         RXB2_READ_CHNN[4:0]               <= RXB2_READ_CHNN[4:0] +5'd1;
   end
end
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      RXB2_WRITE_CHNN[4:0]                 <= 5'd0;
   else begin
      if ( DBIM2_FRM_FCNT9[3:0]==4'd8 && DBIM2_FRM_FCNT270[8:0]==9'd269 && DBIM2_FRM_FCNT8[2:0]==3'd7 )
         RXB2_WRITE_CHNN[4:0]              <= 5'd0;
      else if ( RXB2_WRITE_CHNN[4:0]==5'd23 )
         RXB2_WRITE_CHNN[4:0]              <= 5'd0;
      else
         RXB2_WRITE_CHNN[4:0]              <= RXB2_WRITE_CHNN[4:0] +5'd1;
   end
end

// generate write enable and B2 calculate restart, generated from DBIM2_*
always @( DBIM2_FRM_FCNT270 or DBIM2_FRM_FCNT9 ) begin
   if ( DBIM2_FRM_FCNT9[3:0]==4'd0 && DBIM2_FRM_FCNT270[8:0]<9'd9 )
      RXB2_B2CAL_EN                        <= 1'b0;
   else if ( DBIM2_FRM_FCNT9[3:0]==4'd1 && DBIM2_FRM_FCNT270[8:0]<9'd9 )
      RXB2_B2CAL_EN                        <= 1'b0;
   else if ( DBIM2_FRM_FCNT9[3:0]==4'd2 && DBIM2_FRM_FCNT270[8:0]<9'd9 )
      RXB2_B2CAL_EN                        <= 1'b0;
   else
      RXB2_B2CAL_EN                        <= 1'b1;
end
always @( DBIM2_FRM_FCNT270 or DBIM2_FRM_FCNT9 ) begin
   if ( DBIM2_FRM_FCNT9[3:0]==4'b0 && ( DBIM2_FRM_FCNT270[8:0]==9'd9 || DBIM2_FRM_FCNT270[8:0]==9'd10 || DBIM2_FRM_FCNT270[8:0]==9'd11) )
      RXB2_B2CAL_START                     <= 1'b1;
   else
      RXB2_B2CAL_START                     <= 1'b0;
end

// calculate B2 for every byte
always @( RXB2_B2CAL_START or RXB2_B2CAL_EN or DBIM2_FRM_DATA or RXB2_RO_B2CALC ) begin
   if ( RXB2_B2CAL_EN==1'b1 )  begin
      if ( RXB2_B2CAL_START==1'b1 )
         RXB2_WR_B2CALC[63:0]             <= DBIM2_FRM_DATA[63:0];
      else
         RXB2_WR_B2CALC[63:0]             <= DBIM2_FRM_DATA[63:0] ^ RXB2_RO_B2CALC[63:0];
   end
   else begin
         RXB2_WR_B2CALC[63:0]             <= RXB2_RO_B2CALC[63:0];
   end
end


  assign  B2CALC_RAM_CLKA = DBI_RCLK_155M;
  assign  B2CALC_RAM_CLKB = DBI_RCLK_155M;
  assign  B2CALC_RAM_WEA  = RXB2_B2CAL_EN;
  assign  B2CALC_RAM_ADDRA[5:0]  = { 1'b0, RXB2_WRITE_CHNN[4:0] };
  assign  B2CALC_RAM_ADDRB[5:0]  = { 1'b0, RXB2_READ_CHNN[4:0] };
  assign  B2CALC_RAM_DINA[63:0]  = RXB2_WR_B2CALC[63:0];
  assign  RXB2_RO_B2CALC[63:0]   = B2CALC_RAM_DOUTB[63:0];
 
OH_RSOH_B2RAM_WRAP           INST_B2RAM_CAL(
    .CLKA                    ( B2CALC_RAM_CLKA ),
    .WEA                     ( B2CALC_RAM_WEA ),
    .ADDRA                   ( B2CALC_RAM_ADDRA[5:0] ),
    .DINA                    ( B2CALC_RAM_DINA[63:0] ),
    .CLKB                    ( B2CALC_RAM_CLKB ),
    .ADDRB                   ( B2CALC_RAM_ADDRB[5:0] ),
    .DOUTB                   ( B2CALC_RAM_DOUTB[63:0] )
   );

// capture all B2 result into B2RAM_RESULT at the end of frame
  assign  B2RESULT_RAM_CLKA  = DBI_RCLK_155M;
  assign  B2RESULT_RAM_CLKB  = DBI_RCLK_155M;
  assign  B2RESULT_RAM_WEA   = ( DBIM2_FRM_FCNT9[3:0]==4'd8 && (DBIM2_FRM_FCNT270[8:0]==9'd267 || DBIM2_FRM_FCNT270[8:0]==9'd268 || DBIM2_FRM_FCNT270[8:0]==9'd269) );
  assign  B2RESULT_RAM_ADDRA[5:0]  = { 1'b0, RXB2_WRITE_CHNN[4:0] };
  assign  B2RESULT_RAM_ADDRB[5:0]  = { 1'b0, RXB2_READ_CHNN[4:0] };
  assign  B2RESULT_RAM_DINA[63:0]  = RXB2_WR_B2CALC[63:0];  // same as B2 calculate result
  assign  RXB2_RO_B2RESULT[63:0]   = B2RESULT_RAM_DOUTB[63:0];

OH_RSOH_B2RAM_WRAP           INST_B2RAM_RESULT(
    .CLKA                    ( B2RESULT_RAM_CLKA ),
    .WEA                     ( B2RESULT_RAM_WEA ),
    .ADDRA                   ( B2RESULT_RAM_ADDRA[5:0] ),
    .DINA                    ( B2RESULT_RAM_DINA[63:0] ),
    .CLKB                    ( B2RESULT_RAM_CLKB ),
    .ADDRB                   ( B2RESULT_RAM_ADDRB[5:0] ),
    .DOUTB                   ( B2RESULT_RAM_DOUTB[63:0] )
   );

// accumulate B2 errors when receive B2 bytes of input stream
  assign  RXB2_BITS_ERROR[63:0]   =DBIM2_FRM_DATA[63:0] ^ RXB2_RO_B2RESULT[63:0]; // compare received B2 bytes with saved B2 result

always @( DBIM2_FRM_FCNT270 or DBIM2_FRM_FCNT9 ) begin
   if ( DBIM2_FRM_FCNT9[3:0]==4'd4 && (DBIM2_FRM_FCNT270[8:0]==9'd0 || DBIM2_FRM_FCNT270[8:0]==9'd1 || DBIM2_FRM_FCNT270[8:0]==9'd2) )
      RXB2_B2BYTE_EN            <= 1'b1;
   else
      RXB2_B2BYTE_EN            <= 1'b0;
end
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 ) begin
      RXB2_CHECK_CNT0[7:0]         <= 8'd0;
      RXB2_CHECK_CNT1[7:0]         <= 8'd0;
      RXB2_CHECK_CNT2[7:0]         <= 8'd0;
      RXB2_CHECK_CNT3[7:0]         <= 8'd0;
      RXB2_CHECK_CNT4[7:0]         <= 8'd0;
      RXB2_CHECK_CNT5[7:0]         <= 8'd0;
      RXB2_CHECK_CNT6[7:0]         <= 8'd0;
      RXB2_CHECK_CNT7[7:0]         <= 8'd0;
   end
   else begin
      if ( DBIM2_FRM_FCNT9[3:0]==4'd0 ) begin // clear B2 errors count at the start of the frame
         RXB2_CHECK_CNT0[7:0]      <= 8'd0;
         RXB2_CHECK_CNT1[7:0]      <= 8'd0;
         RXB2_CHECK_CNT2[7:0]      <= 8'd0;
         RXB2_CHECK_CNT3[7:0]      <= 8'd0;
         RXB2_CHECK_CNT4[7:0]      <= 8'd0;
         RXB2_CHECK_CNT5[7:0]      <= 8'd0;
         RXB2_CHECK_CNT6[7:0]      <= 8'd0;
         RXB2_CHECK_CNT7[7:0]      <= 8'd0;
      end
      else if ( RXB2_B2BYTE_EN==1'b1 ) begin
         RXB2_CHECK_CNT0[7:0]      <= RXB2_CHECK_CNT0[7:0] + {7'd0, RXB2_BITS_ERROR[0]} + {7'd0, RXB2_BITS_ERROR[1]} + {7'd0, RXB2_BITS_ERROR[2]} + {7'd0, RXB2_BITS_ERROR[3]} + {7'd0, RXB2_BITS_ERROR[4]} + {7'd0, RXB2_BITS_ERROR[5]} + {7'd0, RXB2_BITS_ERROR[6]} + {7'd0, RXB2_BITS_ERROR[7]};
         RXB2_CHECK_CNT1[7:0]      <= RXB2_CHECK_CNT1[7:0] + {7'd0, RXB2_BITS_ERROR[8]} + {7'd0, RXB2_BITS_ERROR[9]} + {7'd0, RXB2_BITS_ERROR[10]} +{7'd0, RXB2_BITS_ERROR[11]}+ {7'd0, RXB2_BITS_ERROR[12]}+ {7'd0, RXB2_BITS_ERROR[13]}+ {7'd0, RXB2_BITS_ERROR[14]}+ {7'd0, RXB2_BITS_ERROR[15]};
         RXB2_CHECK_CNT2[7:0]      <= RXB2_CHECK_CNT2[7:0] + {7'd0, RXB2_BITS_ERROR[16]}+ {7'd0, RXB2_BITS_ERROR[17]}+ {7'd0, RXB2_BITS_ERROR[18]} +{7'd0, RXB2_BITS_ERROR[19]}+ {7'd0, RXB2_BITS_ERROR[20]}+ {7'd0, RXB2_BITS_ERROR[21]}+ {7'd0, RXB2_BITS_ERROR[22]}+ {7'd0, RXB2_BITS_ERROR[23]};
         RXB2_CHECK_CNT3[7:0]      <= RXB2_CHECK_CNT3[7:0] + {7'd0, RXB2_BITS_ERROR[24]}+ {7'd0, RXB2_BITS_ERROR[25]}+ {7'd0, RXB2_BITS_ERROR[26]} +{7'd0, RXB2_BITS_ERROR[27]}+ {7'd0, RXB2_BITS_ERROR[28]}+ {7'd0, RXB2_BITS_ERROR[29]}+ {7'd0, RXB2_BITS_ERROR[30]}+ {7'd0, RXB2_BITS_ERROR[31]};
         RXB2_CHECK_CNT4[7:0]      <= RXB2_CHECK_CNT4[7:0] + {7'd0, RXB2_BITS_ERROR[32]}+ {7'd0, RXB2_BITS_ERROR[33]}+ {7'd0, RXB2_BITS_ERROR[34]} +{7'd0, RXB2_BITS_ERROR[35]}+ {7'd0, RXB2_BITS_ERROR[36]}+ {7'd0, RXB2_BITS_ERROR[37]}+ {7'd0, RXB2_BITS_ERROR[38]}+ {7'd0, RXB2_BITS_ERROR[39]};
         RXB2_CHECK_CNT5[7:0]      <= RXB2_CHECK_CNT5[7:0] + {7'd0, RXB2_BITS_ERROR[40]}+ {7'd0, RXB2_BITS_ERROR[41]}+ {7'd0, RXB2_BITS_ERROR[42]} +{7'd0, RXB2_BITS_ERROR[43]}+ {7'd0, RXB2_BITS_ERROR[44]}+ {7'd0, RXB2_BITS_ERROR[45]}+ {7'd0, RXB2_BITS_ERROR[46]}+ {7'd0, RXB2_BITS_ERROR[47]};
         RXB2_CHECK_CNT6[7:0]      <= RXB2_CHECK_CNT6[7:0] + {7'd0, RXB2_BITS_ERROR[48]}+ {7'd0, RXB2_BITS_ERROR[49]}+ {7'd0, RXB2_BITS_ERROR[50]} +{7'd0, RXB2_BITS_ERROR[51]}+ {7'd0, RXB2_BITS_ERROR[52]}+ {7'd0, RXB2_BITS_ERROR[53]}+ {7'd0, RXB2_BITS_ERROR[54]}+ {7'd0, RXB2_BITS_ERROR[55]};
         RXB2_CHECK_CNT7[7:0]      <= RXB2_CHECK_CNT7[7:0] + {7'd0, RXB2_BITS_ERROR[56]}+ {7'd0, RXB2_BITS_ERROR[57]}+ {7'd0, RXB2_BITS_ERROR[58]} +{7'd0, RXB2_BITS_ERROR[59]}+ {7'd0, RXB2_BITS_ERROR[60]}+ {7'd0, RXB2_BITS_ERROR[61]}+ {7'd0, RXB2_BITS_ERROR[62]}+ {7'd0, RXB2_BITS_ERROR[63]};
	  end
   end
end

always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      RXB2_CHECK_CNT[11:0]        <= 12'd0;
   else
      RXB2_CHECK_CNT[11:0]        <= {4'd0, RXB2_CHECK_CNT0[7:0]} +{4'd0, RXB2_CHECK_CNT1[7:0]} +{4'd0, RXB2_CHECK_CNT2[7:0]} +{4'd0, RXB2_CHECK_CNT3[7:0]} +{4'd0, RXB2_CHECK_CNT4[7:0]} +{4'd0, RXB2_CHECK_CNT5[7:0]} +{4'd0, RXB2_CHECK_CNT6[7:0]} +{4'd0, RXB2_CHECK_CNT7[7:0]};
end






//****** Section 4: CPU interface B2 and REI count control ******//

// capture M0,M1 byte from data stream
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      CNT_M0M1_BYTE[15:0]               <= 16'd0;
   else if ( DBIM2_FRM_FCNT9[3:0]==4'd8 && DBIM2_FRM_FCNT270[8:0]==9'd3 && DBIM2_FRM_FCNT8[2:0]==3'd0 )
      CNT_M0M1_BYTE[15:0]               <= DBIM2_FRM_DATA[55:40];
end

// B2 and REI count generate
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      MPI_RXB2COUNT[11:0]              <= 12'd0;
   else begin
      if ( DBIM2_FRM_FCNT9[3:0]==4'd8 && DBIM2_FRM_FCNT270[8:0]==9'd269 && DBIM2_FRM_FCNT8[2:0]==3'd7 )
         MPI_RXB2COUNT[11:0]           <= RXB2_CHECK_CNT[11:0];
   end
end
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      MPI_RXB2PULSE                    <= 1'b0;
   else begin
      if ( DBIM2_FRM_FCNT9[3:0]==4'd8 && DBIM2_FRM_FCNT270[8:0]==9'd269 && DBIM2_FRM_FCNT8[2:0]==3'd7 && RXB2_CHECK_CNT[11:0]!=12'd0 )
         MPI_RXB2PULSE                 <= 1'b1;
      else if ( DBIM2_FRM_FCNT9[3:0]==4'd0 && DBIM2_FRM_FCNT270[8:0]==9'd0 && DBIM2_FRM_FCNT8[2:0]==3'd7 )
         MPI_RXB2PULSE                 <= 1'b0;
   end
end

always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      MPI_RXREICOUNT[11:0]             <= 12'd0;
   else begin
      if ( DBIM2_FRM_FCNT9[3:0]==4'd8 && DBIM2_FRM_FCNT270[8:0]==9'd269 && DBIM2_FRM_FCNT8[2:0]==3'd7 )
         MPI_RXREICOUNT[11:0]          <= CNT_M0M1_BYTE[11:0];
   end
end
always @( posedge DBI_RCLK_155M or posedge GLB_RESET ) begin
   if ( GLB_RESET==1'b1 )
      MPI_RXREIPULSE                    <= 1'b0;
   else begin
      if ( DBIM2_FRM_FCNT9[3:0]==4'd8 && DBIM2_FRM_FCNT270[8:0]==9'd269 && DBIM2_FRM_FCNT8[2:0]==3'd7 && CNT_M0M1_BYTE[11:0]!=12'd0 )
         MPI_RXREIPULSE                 <= 1'b1;
      else if ( DBIM2_FRM_FCNT9[3:0]==4'd0 && DBIM2_FRM_FCNT270[8:0]==9'd0 && DBIM2_FRM_FCNT8[2:0]==3'd7 )
         MPI_RXREIPULSE                 <= 1'b0;
   end
end
endmodule
